package com.sailing.xjpb.orm.repository.impl;

import com.sailing.xjpb.orm.repository.SailingJpaRepository;
import org.springframework.data.domain.Page;
import org.springframework.data.domain.Pageable;
import org.springframework.data.jpa.domain.Specification;
import org.springframework.data.jpa.repository.support.JpaEntityInformation;
import org.springframework.data.jpa.repository.support.SimpleJpaRepository;
import org.springframework.data.support.PageableExecutionUtils;

import javax.persistence.EntityManager;
import javax.persistence.TypedQuery;
import java.io.Serializable;
import java.util.List;

public class SailingJpaRepositoryImpl<T, ID extends Serializable> extends SimpleJpaRepository<T, ID>
        implements SailingJpaRepository<T> {

    public SailingJpaRepositoryImpl(JpaEntityInformation<T, ?> entityInformation, EntityManager entityManager) {
        super(entityInformation, entityManager);
    }

    public SailingJpaRepositoryImpl(Class<T> domainClass, EntityManager entityManager) {
        super(domainClass, entityManager);
    }

    @Override
    public Page<T> pageQuickly(Pageable pageable, Specification<T> spec) {
        TypedQuery<T> query = this.getQuery(spec, pageable);
        query.setFirstResult((int) pageable.getOffset());
        query.setMaxResults(pageable.getPageSize() + 1);
        List<T> countList = query.getResultList();
        long currentCount = countList.size();
        long offset = pageable.getOffset();
        boolean hasMoreResult = currentCount > pageable.getPageSize();
        long total = hasMoreResult ? offset + currentCount : currentCount;
        if (hasMoreResult) {
            countList.remove(countList.size() - 1);
        }
        return PageableExecutionUtils.getPage(countList, pageable, () -> total);
    }

}
